package castledefense.game.render.effects;

import castledefense.data.GameData;
import castledefense.data.Resources;
import castledefense.logic.Targetable;

import com.badlogic.gdx.graphics.g2d.ParticleEffect;
import com.badlogic.gdx.graphics.g2d.SpriteBatch;

public class DebuffHandler {

	private final static int MAX = 64;
	private ParticleEffect blast;
	private final UnitEffect[] pool = new UnitEffect[MAX];
	private boolean[] doable = new boolean[MAX];
	private int current = 0;

	public DebuffHandler(int type) {
		if (type == GameData.fire)
			blast = Resources.fireDotEffect;
		else if (type == GameData.water)
			blast = Resources.waterSlowEffect;
		else if (type == GameData.earth)
			blast = Resources.earthStunEffect;			
		else
			System.out.println("Cant load particle effect type" + type);


		for (int i = 0; i < MAX; i++)
			pool[i] = new UnitEffect(blast, type);
	}

	public void dispose() {
		for (int i = 0; i < MAX; i++) {
			pool[i].dispose();
		}
	}

	public void render(SpriteBatch spriteBatch, float delta) {

		for (int i = 0; i < MAX; i++) {
			if (doable[i]) {
				pool[i].render(spriteBatch, delta);				
			}
		}
	}

	public void update(int delta) {

		for (int i = 0; i < MAX; i++) {
			if (doable[i]) {
				doable[i] = pool[i].update();
			}
		}
	}

	public void addBlast(Targetable target, int duration) {
		pool[current].set(target, duration);
		doable[current] = true;
		current++;
		if (current >= MAX) {
			current = 0;
		}
	}

	private class UnitEffect {
		private ParticleEffect blast;
		private Targetable unit = null;
		private final int type;

		public UnitEffect(ParticleEffect blast, int type) {
			this.blast = new ParticleEffect(blast);
			this.type = type;
			// with this emitter can be scaled
			// this.blast.getEmitters().get(0).getScale().setHighMax(this.blast.getEmitters().get(0).getScale().getHighMax()*1.6f);
		}

		public void dispose() {
			blast.dispose();
		}

		public void render(SpriteBatch spriteBatch, float delta) {
			blast.draw(spriteBatch, delta);
		}

		/**
		 * update method. Report true if effect is finished and can be freed to pool
		 */
		public boolean update() {		

			int tmp = 0;
			if (type == GameData.fire) {
				tmp = unit.getDotDuration();
			} else if (type == GameData.water) {
				tmp = unit.getSlowTime();
			} else if (type == GameData.earth) {
				tmp = unit.getStunTime();
			}			
			blast.setDuration(tmp);
			setPos();

			if (blast.isComplete()) {
				unit = null;
				return false;
			}

			return true;
		}

		public void set(Targetable target, int duration) {
			this.unit = target;
			blast.start();
			blast.setDuration(duration);
		}

		private void setPos() {
			blast.setPosition(unit.getRenderingCenterX(), unit.getRenderingCenterY());
		}

	}

}
